import Global from './settings';
import { getDictValueList, getColorNode, getDictKeyList } from './support';
import { ResManager } from './custom/ResManager';

// Learn TypeScript:
//  - https://docs.cocos.com/creator/manual/en/scripting/typescript.html
// Learn Attribute:
//  - https://docs.cocos.com/creator/manual/en/scripting/reference/attributes.html
// Learn life-cycle callbacks:
//  - https://docs.cocos.com/creator/manual/en/scripting/life-cycle-callbacks.html


let HEALTH_BAR_WIDTH = Global.HEALTH_BAR_WIDTH
let BAR_HEIGHT = Global.BAR_HEIGHT
let ENERGY_BAR_WIDTH = Global.ENERGY_BAR_WIDTH
let weapon_data = Global.weapon_data
let magic_data = Global.magic_data
let UI_FONT = "font"
let UI_FONT_SIZE = Global.UI_FONT_SIZE
let UI_BG_COLOR = Global.UI_BG_COLOR
let UI_BORDER_COLOR = Global.UI_BORDER_COLOR
let HEALTH_COLOR = cc.Color.RED
let ENERGY_COLOR = cc.Color.BLUE
let ITEM_BOX_SIZE = Global.ITEM_BOX_SIZE
let UI_BORDER_COLOR_ACTIVE = cc.Color.ORANGE

export default class UI {

    font : cc.Font
    health_bar_rect : cc.Rect
    energy_bar_rect : cc.Rect
    weapon_graphics
    magic_graphics

    parent : cc.Node

    hpBar : Bar
    mpBar : Bar
    expLabel : cc.Label

    weaponBox : SelectBox
    magicBox : SelectBox

    constructor() {

        this.parent = cc.find('Canvas/map/UI')

        this.font = ResManager.getInstance().getRes()[UI_FONT]

		// bar setup 
		this.health_bar_rect = new cc.Rect(10,10,HEALTH_BAR_WIDTH,BAR_HEIGHT)
		this.energy_bar_rect = new cc.Rect(10,34,ENERGY_BAR_WIDTH,BAR_HEIGHT)

		// convert weapon dictionary
		this.weapon_graphics = []
		for(let weapon of getDictValueList(weapon_data)) {
			let path = weapon['graphic']
			this.weapon_graphics.push(weapon)
        }

		// convert magic dictionary
		this.magic_graphics = []
		for(let magic of getDictValueList(magic_data)) {
			this.magic_graphics.push(magic)
        }

        this.hpBar = new Bar(this.parent, this.health_bar_rect.width, this.health_bar_rect.height, HEALTH_COLOR)
        this.mpBar = new Bar(this.parent, this.energy_bar_rect.width, this.energy_bar_rect.height, ENERGY_COLOR)
        this.addChild(this.hpBar, this.health_bar_rect.center.x, this.health_bar_rect.center.y)
        this.addChild(this.mpBar, this.energy_bar_rect.center.x, this.energy_bar_rect.center.y)

        this.weaponBox = new SelectBox(10, 630)
        this.magicBox = new SelectBox(80,635)

        this.parent.addChild(this.weaponBox)
        this.parent.addChild(this.magicBox)

        

        this.create_exp_node()
    }

    create_exp_node() {

        let width = 80
        let height = 40
        let bgWidth = width-3*2
        let bgHeight = height-3*2

        let bg = getColorNode(bgWidth, bgHeight)
        bg.color = new cc.Color().fromHEX(UI_BG_COLOR)
        bg.setContentSize(cc.size(bgWidth, bgHeight))

        let border = getColorNode(width, height)
        border.color = new cc.Color().fromHEX(UI_BORDER_COLOR)
        border.setContentSize(cc.size(width, height))

        let label = new cc.Node()
        let text = label.addComponent(cc.Label)
        text.font = ResManager.getInstance().getRes()['font']
        text.string = "0000"
        text.fontSize = UI_FONT_SIZE
        label.setPosition(0, -bgHeight/2)

        border.addChild(bg)
        border.addChild(label)
        this.parent.addChild(border)

        let x = cc.winSize.width/2 - width/2 - 15
        let y = - cc.winSize.height/2 + height/2 + 15
        border.setPosition(x, y)

        this.expLabel = text
    }

    show_bar(hp,hp_max, mp, mp_max) {

        if(hp < 0) {
            hp = 0
        }
        if(mp < 0) {
            mp = 0
        }

        this.hpBar.showBar(hp, hp_max)
        this.mpBar.showBar(mp, mp_max)
    }

    addChild(node : cc.Node, x, y) {

        let posx = -cc.winSize.width / 2 + node.getContentSize().width/2 + x
        let posy = cc.winSize.height / 2 - node.getContentSize().height/2 - y

        node.setPosition(posx, posy)
        node.zIndex = cc.macro.MAX_ZINDEX
        this.parent.addChild(node)
    }

    show_exp(exp) {
        this.expLabel.string = "" + Math.floor(exp)
    }

    weapon_overlay(weapon_index,has_switched) {
        let key = getDictKeyList(weapon_data)[weapon_index]
        let sp = ResManager.getInstance().getRes()[key]["full"]
        this.weaponBox.setImage(sp)
        this.weaponBox.show(has_switched)
    }

    magic_overlay(magic_index,has_switched) {
        let key = getDictKeyList(magic_data)[magic_index]
        let sp = ResManager.getInstance().getRes()[key+"_icon"]
        this.magicBox.setImage(sp)
        this.magicBox.show(has_switched)
    }

    display(player) {
        this.show_bar(player.health, player.stats['health'], player.energy, player.stats['energy'])
		this.show_exp(player.exp)

		this.weapon_overlay(player.weapon_index, !player.can_switch_weapon)
		this.magic_overlay(player.magic_index, !player.can_switch_magic)

    }

}

class Bar extends cc.Node {
    
    bgWidth 
    bgHeight
    bar 

    constructor(parent : cc.Node, width, height, barColor:cc.Color) {

        super()

        let bgWidth = width-3*2
        let bgHeight = height-3*2

        this.bgWidth = bgWidth
        this.bgHeight = bgHeight
        
        // draw bg
        let bg = getColorNode(bgWidth, bgHeight)
        bg.color = new cc.Color().fromHEX(UI_BG_COLOR)
        bg.setContentSize(cc.size(bgWidth, bgHeight))

        let border = getColorNode(width, height)
        border.color = new cc.Color().fromHEX(UI_BORDER_COLOR)
        border.setContentSize(cc.size(width, height))

        // drawing the bar
        let bar = getColorNode(bgWidth, bgHeight) 
        bar.color = barColor
        bar.setContentSize(cc.size(bgWidth, bgHeight))
        bar.setPosition(-bgWidth/2, 0)
        bar.setAnchorPoint(cc.v2(0, 0.5))
        this.bar = bar

        this.addChild(border)
        this.addChild(bg)
        this.addChild(bar)

    }

    showBar(current, max_amount) {
		let ratio = current / max_amount
		let barWidth = this.bgWidth * ratio
        this.bar.setContentSize(cc.size(barWidth, this.bgHeight))
    }

}

class SelectBox extends cc.Node {

    selectNode : cc.Node
    img : cc.Sprite

    constructor(left, top) {
        super()
        let width = ITEM_BOX_SIZE
        let height = ITEM_BOX_SIZE
        let bgWidth = width-3*2
        let bgHeight = height-3*2

        let bg = getColorNode(bgWidth, bgHeight)
        bg.color = new cc.Color().fromHEX(UI_BG_COLOR)

        let border1 = getColorNode(width, height)
        border1.color = new cc.Color().fromHEX(UI_BORDER_COLOR)

        let border2 = getColorNode(width, height)
        border2.color = UI_BORDER_COLOR_ACTIVE

        let imgNode = new cc.Node()
        let img = imgNode.addComponent(cc.Sprite)   
        this.img = img


        this.addChild(border1)
        this.addChild(bg)
        this.addChild(border2)
        this.addChild(imgNode)

        this.selectNode = border2
        this.selectNode.active = false

        let x = -cc.winSize.width/2 + width/2 + left
        let y = (cc.winSize.height - top) + (-cc.winSize.height/2) - height/2
        this.setPosition(x, y)
    }

    show(isSelect) {
        this.selectNode.active = isSelect
    }

    setImage(sp : cc.SpriteFrame) {
        this.img.spriteFrame = sp
    }

}